package com.sk.ccflower.server.match;

import java.io.File;
import java.util.Random;

import javax.jms.MessageConsumer;
import javax.jms.ObjectMessage;

import org.apache.log4j.Logger;

import com.sk.ccflower.lib.define.BaseCfg;
import com.sk.ccflower.lib.define.Consts;
import com.sk.ccflower.lib.pfBeans.ProfileBean;
import com.sk.ccflower.server.lib.dbBeans.CfProfileBean;
import com.sk.ccflower.server.lib.dbBeans.MfMatchBean;
import com.sk.ccflower.server.lib.dbUtils.DBConnection;
import com.sk.ccflower.server.lib.dbUtils.qry.CfProfileQry;
import com.sk.ccflower.server.lib.dbUtils.qry.MfMatchQry;
import com.sk.ccflower.server.lib.sysUtils.Environment;
import com.sun.messaging.ConnectionConfiguration;
import com.sun.messaging.ConnectionFactory;
import com.sun.messaging.Destination;
import com.sun.messaging.jms.Connection;
import com.sun.messaging.jms.JMSException;
import com.sun.messaging.jms.Message;
import com.sun.messaging.jms.Session;

public class MatchingQueueThread extends Thread {
	
	private Logger m_log;
	private ConnectionFactory m_fac = null;
	private Connection m_connection = null;
	private Session m_session = null;
	private Destination m_dest = null;
	private MessageConsumer m_consumer = null;
	private MatchingCenter m_parent = null;
	
	public MatchingQueueThread(MatchingCenter _parent) {
		this.m_log = Logger.getLogger( getClass() );
		this.m_parent = _parent;
	}
	
	private void connectBroker() {
		try {
			m_fac = new ConnectionFactory();
			m_fac.setProperty( ConnectionConfiguration.imqAddressList, BaseCfg.MESSAGE_QUEUE_SERVER_URL );
			m_fac.setProperty( ConnectionConfiguration.imqReconnectEnabled, "true" );
			
			m_connection = (Connection) m_fac.createConnection();
			
			m_session = (Session) m_connection.createSession( false, Session.AUTO_ACKNOWLEDGE );
			
			m_dest = new com.sun.messaging.Queue( Consts.MESSAGE_QUEUE_NAME.MATCHING );
			
			m_consumer = m_session.createConsumer( m_dest );
			
			m_connection.start();
		} catch ( Exception e ) {
			try {
				Thread.sleep( 1000 );
			} catch ( Exception e1 ) {
				e1.printStackTrace();
				m_log.error( e1 );
			}
			connectBroker();
		}
	}
	
	private void newMatching( ProfileBean bean ) throws Exception {
		java.sql.Connection conn = null;
		DBConnection dbConn = null;
		String path = null;
		
		try {
			path = Environment.getDataProfileDir();
			path += File.separator + bean.email;
			path += File.separator + "matching.lst";
			
			conn = (java.sql.Connection) m_parent.connectionPool.getConnection();
			dbConn = new DBConnection( conn );
			//dbConn = new DBConnection( BaseCfg.JDBC_URL, BaseCfg.JDBC_USER, BaseCfg.JDBC_PWD );
			CfProfileQry pQry = new CfProfileQry( dbConn );
			MfMatchQry mQry = new MfMatchQry( dbConn );
			
			// 남자 : 여자 매칭
			if ( bean.sex == Consts.SEX.MAN ) {
				pQry.selectBySex( Consts.SEX.WOMAN );
			}
			
			// 여자 : 남자 매칭
			if ( bean.sex == Consts.SEX.WOMAN ) {
				pQry.selectBySex( Consts.SEX.MAN );
			}
			
			Random r = new Random( System.currentTimeMillis() );
			int successCount = 0;
			int matchingCount = ( BaseCfg.DAILY_MATCHING_COUNT > pQry.m_arr.size() ? pQry.m_arr.size() : BaseCfg.DAILY_MATCHING_COUNT );
			
			while ( true ) {
				if ( successCount == matchingCount )		break;
				
				mQry.select( bean.email );
				int matchedCount = mQry.m_arr.size();
				if ( matchedCount >= pQry.m_arr.size() )	break;
				
				// 임시로 매칭상대를 랜덤으로 생성 ㅡ.ㅡ
				int n = r.nextInt( pQry.m_arr.size() );
				
				CfProfileBean pBean = (CfProfileBean) pQry.m_arr.get(n);
				MfMatchBean mBean = new MfMatchBean();
				mBean.src_user = bean.email;
				mBean.dest_user = pBean.email;
				
				try {
					mQry.insert( mBean );
					successCount++;
					m_log.info( "["+bean.email+"]님에게 새로운 이성 ["+pBean.email+"]을 매칭했습니다." );
					Thread.sleep( 10 );
				} catch ( Exception e ) {
					continue;
				}
			}
		} catch ( Exception e ) {
			e.printStackTrace();
			this.m_log.error( e );
		} finally {
			if ( null != conn )		conn.close();
			if ( null != dbConn )	dbConn.close();
		}
	}
	
	public void run() {
		connectBroker();
		ProfileBean bean = null;
		
		while ( true ) {
			try {
				Message inMsg = (Message) m_consumer.receive();
				ObjectMessage objMsg = (ObjectMessage) inMsg;
				
				bean = (ProfileBean) objMsg.getObject();
				if ( null != bean ) {
					newMatching( bean );
				}
				
				Thread.sleep( 10 );
			} catch ( JMSException e ) {
				this.m_log.error( e );
				try {
					if  ( null != m_session )		m_session.close();
					if  ( null != m_connection )	m_connection.close();
					
					connectBroker();
				} catch ( Exception e1 ) {
					this.m_log.error( e1 );
				}
			} catch ( Exception e ) {
				e.printStackTrace();
				this.m_log.error( e );
			}
		}
	}
	
}
